﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace PersistanceLayer
{
    public class InMemoryRepository : IChatBoxDataRepository
    {
        private static IList<IChatBoxUserData> _users = new List<IChatBoxUserData>();
        private static IList<IChatBoxUserData> _offlineUsers=new List<IChatBoxUserData>(); 
        private static int _id = 0;
        public void ChangeIsOnlinePropertyWhenAppropriate(int thresholdInSeconds)
        {
            var onlineUsers = new List<IChatBoxUserData>();
            //     tempUsers.AddRange(from user in _users let timeSpan = DateTime.Now.Subtract(user.LastSeen) where timeSpan.TotalSeconds <= thresholdInSeconds select user);
            foreach (ChatBoxUserData user in _users)
            {
                if (DateTime.Now.Subtract(user.LastSeen).TotalSeconds <= thresholdInSeconds)
                {
                    onlineUsers.Add(user);
                    lock (_users)
                    {
                        user.IsOnline = true;
                    }
                }
                else
                {
                    if(user.IsRegistered)
                    {
                        lock (_users)
                        {
                            user.IsOnline = false;
                        }
                        _offlineUsers.Add(user);
                    }
               }
            }
            lock (_users)
            {
                _users = onlineUsers;
            }
            
        }

        public IChatBoxUserData AddUserWhenNameIsNew(string name, double lat, double lon, string iconUrl)
        {
            lock (_users)
            {

                foreach (IChatBoxUserData u in _users)
                {
                    if (u.Name.Equals(name))
                    {
                        return null;
                    }
                }
                _id++;
                ChatBoxUserData user = new ChatBoxUserData(_id, name, iconUrl, true, "", lat, lon,false);

                //     user.LastSeen = DateTime.Now;
                _users.Add(user);
                return user;
            }
        }


        public IChatBoxUserData AddUserWhenNameIsNew(string name, double lat, double lon, string iconUrl, string nickName)
        {
            lock (_users)
        {
                foreach (IChatBoxUserData u in _users)
                {
                    if (u.Name.Equals(name))
                    {
                        return null;
                    }
                } 
            _id++;
            ChatBoxUserData user = new ChatBoxUserData(_id, name, iconUrl, true, nickName, lat, lon,true);
            _users.Add(user);
            return user;
 }
     
    }

        public List<IChatBoxUserData> GetAllUsersOnline()
        {
            return (List<IChatBoxUserData>)_users;
        }

        public void ClearUsers()
        {
            lock (_users)
            {
 
            _users.Clear();
            }
        }

        public void UpdateLastSeen(int id)
        {
            IChatBoxUserData user = _users.ToList().FindLast(e => e.Id == id);
            if (user != null)
                user.SetLastSeen(DateTime.Now);
        }


        public void LoginRegisteredUser(int id)
        {
            foreach (IChatBoxUserData user in _offlineUsers)
            {
                if(user.Id == id)
                {
                    user.SetLastSeen(DateTime.Now);
                    user.SetIsOnline(true);
                    _users.Add(user);
                }
            }
        }

        private static IList<IChatBoxMessageData> _messages = new List<IChatBoxMessageData>(); 
        public IList<IChatBoxMessageData> GetLastMessages(int id)
        {
            UpdateLastSeen(id);

            if (GetAllUsersOnline().FindLast(e => e.Id == id) == null)
            {
                return new List<IChatBoxMessageData>();
            }
            var lastMessages = _messages.Skip(Math.Max(0, _messages.Count() - 5)).Take(5);
            var listMessages = new List<IChatBoxMessageData>();
            foreach (var m in lastMessages)
            {
                listMessages.Add(m);
            }
            return listMessages;
        }


        public bool SendMessage(int id, string message)
        {
            var user = GetAllUsersOnline().FindLast(e => e.Id == id);
            if (user == null) return false;
            else
            {
                _messages.Add(new ChatBoxMessageData(user, message));
                return true;
            }
        }
        private static IChatBoxUserData FindUser(IList<IChatBoxUserData> list, string name)
        {
            foreach (var user in list)
            {
                if (string.Equals(user.Name, name))
                    return user;
            }
            return null;
        }
    }
}
